package com.yuerlive.rainbow.nim;

import android.content.Context;
import android.text.TextUtils;

import com.netease.nimlib.sdk.NIMClient;
import com.netease.nimlib.sdk.Observer;
import com.netease.nimlib.sdk.RequestCallback;
import com.netease.nimlib.sdk.StatusCode;
import com.netease.nimlib.sdk.auth.AuthService;
import com.netease.nimlib.sdk.auth.AuthServiceObserver;
import com.netease.nimlib.sdk.auth.LoginInfo;
import com.netease.nimlib.sdk.chatroom.ChatRoomMessageBuilder;
import com.netease.nimlib.sdk.chatroom.ChatRoomService;
import com.netease.nimlib.sdk.chatroom.ChatRoomServiceObserver;
import com.netease.nimlib.sdk.chatroom.constant.MemberQueryType;
import com.netease.nimlib.sdk.chatroom.model.ChatRoomInfo;
import com.netease.nimlib.sdk.chatroom.model.ChatRoomMember;
import com.netease.nimlib.sdk.chatroom.model.ChatRoomMemberUpdate;
import com.netease.nimlib.sdk.chatroom.model.ChatRoomMessage;
import com.netease.nimlib.sdk.chatroom.model.EnterChatRoomData;
import com.netease.nimlib.sdk.chatroom.model.EnterChatRoomResultData;
import com.netease.nimlib.sdk.msg.MsgService;
import com.netease.nimlib.sdk.uinfo.UserService;
import com.netease.nimlib.sdk.uinfo.constant.UserInfoFieldEnum;
import com.yuerlive.rainbow.API;
import com.yuerlive.rainbow.entity.User;
import com.yuerlive.rainbow.entity.UserInfo;
import com.yuerlive.rainbow.utils.DeviceUtils;
import com.yuerlive.rainbow.utils.L;
import com.yuerlive.rainbow.utils.PreferenceUtils;
import com.yuerlive.rainbow.utils.ProcessUtil;
import com.yuerlive.rainbow.utils.UserProxy;
import com.yuerlive.rainbow.widget.timeselector.TextUtil;

import java.lang.annotation.Target;
import java.lang.ref.WeakReference;
import java.nio.channels.CancelledKeyException;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.WeakHashMap;

/**
 * Created by xiaoyi on 2017/5/23.
 */

public class NimHelper {
    private final static String vacationer_key = "nim_vacationer";
    private static String TAG = "NimHelper";
    /*角色*/
    public static final String CHARACTER_NORMAL = "NORMAL";  //普通
    public static final String CHARACTER_ADMIN = "ADMIN";    //管理员
    public static final String CHARACTER_ANCHOR = "ANCHOR";  //主播
    public static final String KEY_CHARACTER = "CHARACTER";  //主播


    private NimHelper() {
    }

    public static void init(Context context) {
        if (ProcessUtil.inMainProcess(context)) {
            NIMClient.init(context.getApplicationContext(), getLoginInfo(context), null);

            NIMClient.getService(MsgService.class).registerCustomAttachmentParser(new CustomAttachParser());
        }
    }

    private static LoginInfo getLoginInfo(Context context) {
        User user = UserProxy.getUser();
        if (user != null) {
            String id = user.getUserId();
            String token = user.getToken();
            return generateLoginInfo(id, token);
//            return null;
        } else {
            //return generateVacationer(context);
            /*User u = new User();
            u.setUserId("1000068");
            u.setToken("b26ee5c78f71400fa0ae65850664078a");
            UserInfo info = new UserInfo();
            u.setUserInfo(info);
            UserProxy.setUser(u);
            return generateLoginInfo(u.getUserId(), u.getUserId());*/
            return null;
        }
    }

    private static LoginInfo generateVacationer(Context context) {
        String vacationer = PreferenceUtils.getString(vacationer_key);
        if (TextUtil.isEmpty(vacationer)) {
            vacationer = generateVacationerCount(context);
            PreferenceUtils.putString(vacationer_key, vacationer);
        }
        return new LoginInfo(vacationer, vacationer);
    }

    private static String generateVacationerCount(Context context) {
        return DeviceUtils.getDeviceId(context);
    }

    public static LoginInfo generateLoginInfo(String id, String token) {

        if (API.HOST.equals("http://qa.api.yuerlive.cn/")) {
            return new LoginInfo("test_" + id, id);
        } else if (API.HOST.equals("https://api.yuerlive.cn/")) {
            return new LoginInfo(id, id);
        } else if (API.HOST.equals("http://47.95.32.135:28888/")) {
            return new LoginInfo("test_" + id, id);
        } else {
            return new LoginInfo(id, id);
        }
    }

    public static void login(LoginInfo info) {
        NIMClient.getService(AuthService.class).login(info).setCallback(new RequestCallback() {
            @Override
            public void onSuccess(Object param) {
                L.e(TAG, "login success");
            }

            @Override
            public void onFailed(int code) {
                L.e(TAG, "login onFailed code " + code);
            }

            @Override
            public void onException(Throwable exception) {
                L.e(TAG, "login exception " + exception.getCause());
            }
        });
    }

    public static void login(LoginInfo info, RequestCallback callback) {
        WeakReference<RequestCallback> weakReference = new WeakReference<RequestCallback>(callback);
        NIMClient.getService(AuthService.class).login(info).setCallback(weakReference.get());
    }

    public static void logout() {
        NIMClient.getService(AuthService.class).logout();
    }

    public static void enterChatRoom(String roomId, EnterChatRoomCallback callback) {
        WeakReference<EnterChatRoomCallback> callbackWeakReference = new WeakReference<EnterChatRoomCallback>(callback);
        EnterChatRoomData data = new EnterChatRoomData(roomId);
        User user = UserProxy.getUser();
        if (user != null) {
            Map<String, Object> extention = new HashMap<>();
            extention.put("level", user.getUserInfo().getLv());
            data.setNick(user.getUserInfo().getNickname());
            if (!TextUtils.isEmpty(user.getUserInfo().getIcon()) && user.getUserInfo().getIcon().startsWith("http")) {
                data.setAvatar(user.getUserInfo().getIcon());
            } else {
                data.setAvatar(API.IMAGE_HOST + user.getUserInfo().getIcon());
            }
            data.setExtension(extention);
        }
        NIMClient.getService(ChatRoomService.class).enterChatRoom(data)
                .setCallback(new RequestCallback<EnterChatRoomResultData>() {
                    @Override
                    public void onSuccess(EnterChatRoomResultData param) {
                        if (callbackWeakReference.get() != null) {
                            updateMyRoomRole(param.getRoomId(), param.getMember());
                            HashMap map = new HashMap();
                            map.put("level", UserProxy.getUser().getUserInfo().getLv());
                            param.getMember().setExtension(map);
                            callbackWeakReference.get().enterSuccess(param);
                        }
                    }

                    @Override
                    public void onFailed(int code) {

                        if (callbackWeakReference.get() != null) {
                            callbackWeakReference.get().enterFaild(code);
                        }
                    }

                    @Override
                    public void onException(Throwable exception) {
                        if (callbackWeakReference.get() != null) {
                            callbackWeakReference.get().enterException(exception);
                        }
                    }
                });
    }


    public static void exitChatRoom(String roomId) {
        NIMClient.getService(ChatRoomService.class).exitChatRoom(roomId);
    }

    public static void sendMessage(String roomId, ChatRoomMessage msg, SendMsgCallback callback) {
        WeakReference<SendMsgCallback> callbackWeakReference = new WeakReference<SendMsgCallback>(callback);
        NIMClient.getService(ChatRoomService.class).sendMessage(msg, false).setCallback(new RequestCallback<Void>() {
            @Override
            public void onSuccess(Void param) {
                if (callbackWeakReference.get() != null)
                    callbackWeakReference.get().sendSuccess(msg);
            }

            @Override
            public void onFailed(int code) {
                if (callbackWeakReference.get() != null)
                    callbackWeakReference.get().sendFaild(code);
            }

            @Override
            public void onException(Throwable exception) {
                if (callbackWeakReference.get() != null)
                    callbackWeakReference.get().sendException(exception);
            }
        });
    }

    public static void registerMsgObserver(OnMessageReceiveListener listener, boolean registered) {
        WeakReference<OnMessageReceiveListener> weakReference = new WeakReference<OnMessageReceiveListener>(listener);
        Observer<List<ChatRoomMessage>> incomingChatRoomMsg = new Observer<List<ChatRoomMessage>>() {
            @Override
            public void onEvent(List<ChatRoomMessage> messages) {
                if (weakReference.get() != null) {
                    for (ChatRoomMessage message : messages) {
                        if (weakReference.get() != null)
                            weakReference.get().onReceive(message);
                    }
                }
            }
        };
        NIMClient.getService(ChatRoomServiceObserver.class)
                .observeReceiveMessage(incomingChatRoomMsg, registered);
    }

    /*更新信息*/
    public static void updateUserInfo(UserInfoFieldEnum key, Object value) {
        Map<UserInfoFieldEnum, Object> fields = new HashMap<>();
        fields.put(key, value);
        NIMClient.getService(UserService.class).updateUserInfo(fields);
    }

    /*获取聊天室成员列表*/
    public static void getChatRoomMember(String roomId, ChatRoomMemberListener listener) {
        WeakReference<ChatRoomMemberListener> reference = new WeakReference<ChatRoomMemberListener>(listener);
        NIMClient.getService(ChatRoomService.class).fetchRoomMembers(roomId,
                MemberQueryType.GUEST, 0, 1000)
                .setCallback(new RequestCallback<List<ChatRoomMember>>() {
                    @Override
                    public void onSuccess(List<ChatRoomMember> param) {
                        if (reference.get() != null)
                            reference.get().getMembers(param);
                    }

                    @Override
                    public void onFailed(int code) {

                    }

                    @Override
                    public void onException(Throwable exception) {

                    }
                });
    }

    /*获取聊天室成员列表*/
    public static void getChatRoomMember(String roomId, ChatRoomMemberListener listener, String ids) {
        WeakReference<ChatRoomMemberListener> reference = new WeakReference<ChatRoomMemberListener>(listener);
        NIMClient.getService(ChatRoomService.class).fetchRoomMembersByIds(roomId,
                Arrays.asList(ids))
                .setCallback(new RequestCallback<List<ChatRoomMember>>() {
                    @Override
                    public void onSuccess(List<ChatRoomMember> param) {
                        if (reference.get() != null)
                            reference.get().getMembers(param);
                    }

                    @Override
                    public void onFailed(int code) {

                    }

                    @Override
                    public void onException(Throwable exception) {

                    }
                });
    }

    /*获取聊天室成员列表*/
    public static void getChatRoomMember(int level, String roomId, ChatRoomMemberListener listener, String ids) {
        WeakReference<ChatRoomMemberListener> reference = new WeakReference<ChatRoomMemberListener>(listener);
        NIMClient.getService(ChatRoomService.class).fetchRoomMembersByIds(roomId,
                Arrays.asList(ids))
                .setCallback(new RequestCallback<List<ChatRoomMember>>() {
                    @Override
                    public void onSuccess(List<ChatRoomMember> param) {
                        if (reference.get() != null && !param.isEmpty()) {
                            param.get(0).setMemberLevel(level);
                            reference.get().getMembers(param);
                        }
                    }

                    @Override
                    public void onFailed(int code) {

                    }

                    @Override
                    public void onException(Throwable exception) {

                    }
                });
    }

    public static void queryChatRoomInfo(String roomId) {
        NIMClient.getService(ChatRoomService.class)
                .fetchRoomInfo(roomId).setCallback(new RequestCallback<ChatRoomInfo>() {
            @Override
            public void onSuccess(ChatRoomInfo param) {
                L.e(TAG, param);
            }

            @Override
            public void onFailed(int code) {
                L.e(TAG, code);
            }

            @Override
            public void onException(Throwable exception) {
                L.e(TAG, exception);
            }
        });
    }

    private static void updateMyRoomRole(String roomId, ChatRoomMember member) {
        ChatRoomMemberUpdate chatRoomMemberUpdate = new ChatRoomMemberUpdate();
        chatRoomMemberUpdate.setNick(member.getNick());
        chatRoomMemberUpdate.setAvatar(member.getAvatar());
        Map<String, Object> params = new HashMap<>();
        params.put("level", UserProxy.getUser().getUserInfo().getLv());
        chatRoomMemberUpdate.setExtension(params);
        NIMClient.getService(ChatRoomService.class)
                .updateMyRoomRole(roomId, chatRoomMemberUpdate, false, null).setCallback(new RequestCallback<Void>() {
            @Override
            public void onSuccess(Void param) {
                L.e(TAG, "nothing");
            }

            @Override
            public void onFailed(int code) {
                L.e(TAG, "code " + code);
            }

            @Override
            public void onException(Throwable exception) {
                L.e(TAG, "exception " + exception);
            }
        });
    }
}
